<!DOCTYPE html>
<html lang="zh-CN">
  <head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width,initial-scale=1">
    <title>文章搜索 | Megasu的笔记</title>
    <meta name="generator" content="VuePress 1.5.4">
    <link rel="icon" href="/heima2020/favicon.ico">
    <meta name="description" content="Megasu的笔记整理">
    <meta name="author" content="Megasu">
    <meta name="Keywords" content="学习网站,前端,分享">
    <link rel="preload" href="/heima2020/assets/css/0.styles.aa663799.css" as="style"><link rel="preload" href="/heima2020/assets/js/app.e2adc9d2.js" as="script"><link rel="preload" href="/heima2020/assets/js/2.7389c9d3.js" as="script"><link rel="preload" href="/heima2020/assets/js/21.85e67b4a.js" as="script"><link rel="prefetch" href="/heima2020/assets/js/10.8b750e5f.js"><link rel="prefetch" href="/heima2020/assets/js/11.9224f975.js"><link rel="prefetch" href="/heima2020/assets/js/12.3ea117b6.js"><link rel="prefetch" href="/heima2020/assets/js/13.7524b74f.js"><link rel="prefetch" href="/heima2020/assets/js/14.cee0fcf8.js"><link rel="prefetch" href="/heima2020/assets/js/15.7a4a27f7.js"><link rel="prefetch" href="/heima2020/assets/js/16.947d882b.js"><link rel="prefetch" href="/heima2020/assets/js/17.79d3becb.js"><link rel="prefetch" href="/heima2020/assets/js/18.48208e3a.js"><link rel="prefetch" href="/heima2020/assets/js/19.3d0c49ef.js"><link rel="prefetch" href="/heima2020/assets/js/20.1f6114c8.js"><link rel="prefetch" href="/heima2020/assets/js/22.ce482f4d.js"><link rel="prefetch" href="/heima2020/assets/js/23.a150bd35.js"><link rel="prefetch" href="/heima2020/assets/js/24.8cd80d5d.js"><link rel="prefetch" href="/heima2020/assets/js/25.0001c7c1.js"><link rel="prefetch" href="/heima2020/assets/js/26.aa4d65a5.js"><link rel="prefetch" href="/heima2020/assets/js/27.baffff1d.js"><link rel="prefetch" href="/heima2020/assets/js/28.20430dcf.js"><link rel="prefetch" href="/heima2020/assets/js/29.7bbc3c04.js"><link rel="prefetch" href="/heima2020/assets/js/3.0076a912.js"><link rel="prefetch" href="/heima2020/assets/js/30.5f74696f.js"><link rel="prefetch" href="/heima2020/assets/js/31.a0bf56d6.js"><link rel="prefetch" href="/heima2020/assets/js/32.dd5a93dd.js"><link rel="prefetch" href="/heima2020/assets/js/33.92de7335.js"><link rel="prefetch" href="/heima2020/assets/js/34.bf468ed6.js"><link rel="prefetch" href="/heima2020/assets/js/35.28502be1.js"><link rel="prefetch" href="/heima2020/assets/js/36.3622a14c.js"><link rel="prefetch" href="/heima2020/assets/js/37.626e17d3.js"><link rel="prefetch" href="/heima2020/assets/js/38.860020b8.js"><link rel="prefetch" href="/heima2020/assets/js/39.c092c283.js"><link rel="prefetch" href="/heima2020/assets/js/4.586af112.js"><link rel="prefetch" href="/heima2020/assets/js/40.a6ba2743.js"><link rel="prefetch" href="/heima2020/assets/js/41.43d70bcd.js"><link rel="prefetch" href="/heima2020/assets/js/42.6486a709.js"><link rel="prefetch" href="/heima2020/assets/js/43.670b256a.js"><link rel="prefetch" href="/heima2020/assets/js/44.eb371480.js"><link rel="prefetch" href="/heima2020/assets/js/45.5b45f11e.js"><link rel="prefetch" href="/heima2020/assets/js/46.bc59be94.js"><link rel="prefetch" href="/heima2020/assets/js/47.ec36fca9.js"><link rel="prefetch" href="/heima2020/assets/js/48.51e80f8f.js"><link rel="prefetch" href="/heima2020/assets/js/5.6eb7e243.js"><link rel="prefetch" href="/heima2020/assets/js/6.1b7d5a6d.js"><link rel="prefetch" href="/heima2020/assets/js/7.f611fe3c.js"><link rel="prefetch" href="/heima2020/assets/js/8.c14cc922.js"><link rel="prefetch" href="/heima2020/assets/js/9.cd5538bb.js">
    <link rel="stylesheet" href="/heima2020/assets/css/0.styles.aa663799.css">
  </head>
  <body>
    <div id="app" data-server-rendered="true"><div class="theme-container"><header class="navbar"><div class="sidebar-button"><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" role="img" viewBox="0 0 448 512" class="icon"><path fill="currentColor" d="M436 124H12c-6.627 0-12-5.373-12-12V80c0-6.627 5.373-12 12-12h424c6.627 0 12 5.373 12 12v32c0 6.627-5.373 12-12 12zm0 160H12c-6.627 0-12-5.373-12-12v-32c0-6.627 5.373-12 12-12h424c6.627 0 12 5.373 12 12v32c0 6.627-5.373 12-12 12zm0 160H12c-6.627 0-12-5.373-12-12v-32c0-6.627 5.373-12 12-12h424c6.627 0 12 5.373 12 12v32c0 6.627-5.373 12-12 12z"></path></svg></div> <a href="/heima2020/" class="home-link router-link-active"><!----> <span class="site-name">Megasu的笔记</span></a> <div class="links"><div class="search-box"><input aria-label="Search" autocomplete="off" spellcheck="false" value=""> <!----></div> <nav class="nav-links can-hide"><div class="nav-item"><a href="/heima2020/" class="nav-link">
  首页
</a></div> <!----></nav></div></header> <div class="sidebar-mask"></div> <aside class="sidebar"><nav class="nav-links"><div class="nav-item"><a href="/heima2020/" class="nav-link">
  首页
</a></div> <!----></nav>  <ul class="sidebar-links"><li><section class="sidebar-group depth-0"><a href="/heima2020/node/day01" class="sidebar-heading clickable open"><span>Node</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/heima2020/node/day01.html" class="sidebar-link">Node 第 1 天</a></li><li><a href="/heima2020/node/day02.html" class="sidebar-link">Node 第 2 天</a></li><li><a href="/heima2020/node/day03.html" class="sidebar-link">Node 第 3 天</a></li><li><a href="/heima2020/node/day04.html" class="sidebar-link">Node 第 4 天</a></li><li><a href="/heima2020/node/day05.html" class="sidebar-link">Node 第 5 天</a></li><li><a href="/heima2020/node/day06.html" class="sidebar-link">Node 第 6 天</a></li><li><a href="/heima2020/node/day07.html" class="sidebar-link">Node 第 7 天</a></li><li><a href="/heima2020/node/day08.html" class="sidebar-link">Node 第 8 天</a></li></ul></section></li></ul> </aside> <main class="page"> <div class="theme-default-content content__default"><h2 id="文章搜索"><a href="#文章搜索" class="header-anchor">#</a> 文章搜索</h2> <img src="/heima2020/assets/img/001 - 文章搜索.38661019.png" style="zoom:60%;"> <h3 id="_1-准备"><a href="#_1-准备" class="header-anchor">#</a> 1. 准备</h3> <h4 id="_1-1-创建组件并配置路由"><a href="#_1-1-创建组件并配置路由" class="header-anchor">#</a> 1.1 创建组件并配置路由</h4> <ol><li>创建 <code>src/views/search/index.vue</code></li></ol> <div class="language-vue extra-class"><pre class="language-vue"><code><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>template</span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>div</span> <span class="token attr-name">class</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>search-container<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>搜索页面<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>div</span><span class="token punctuation">&gt;</span></span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>template</span><span class="token punctuation">&gt;</span></span>

<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>script</span><span class="token punctuation">&gt;</span></span><span class="token script"><span class="token language-javascript">
<span class="token keyword">export</span> <span class="token keyword">default</span> <span class="token punctuation">{</span>
  name<span class="token operator">:</span> <span class="token string">'SearchIndex'</span>
<span class="token punctuation">}</span>
</span></span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>script</span><span class="token punctuation">&gt;</span></span>

<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>style</span> <span class="token attr-name">scoped</span> <span class="token attr-name">lang</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>less<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span><span class="token style"></span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>style</span><span class="token punctuation">&gt;</span></span>
</code></pre></div><ol start="2"><li><p>然后把搜索页面的路由配置到根组件路由（一级路由）</p> <div class="language-js extra-class"><pre class="language-js"><code><span class="token punctuation">{</span>
  path<span class="token operator">:</span> <span class="token string">'/search'</span><span class="token punctuation">,</span>
  name<span class="token operator">:</span> <span class="token string">'search'</span><span class="token punctuation">,</span>
  <span class="token function-variable function">component</span><span class="token operator">:</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">=&gt;</span> <span class="token keyword">import</span><span class="token punctuation">(</span><span class="token string">'@/views/search'</span><span class="token punctuation">)</span>
<span class="token punctuation">}</span>
</code></pre></div></li> <li><p>最后访问 <code>/search</code> 测试</p></li></ol> <h4 id="_1-2-搜索栏页面布局"><a href="#_1-2-搜索栏页面布局" class="header-anchor">#</a> 1.2 搜索栏页面布局</h4> <blockquote><p>使用 <code>Vant</code> 组件提供的<a href="https://youzan.github.io/vant/#/zh-CN/search" target="_blank" rel="noopener noreferrer"> search 组件<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a>实现顶部导航栏的布局</p></blockquote> <ol><li>使用  <code>Vant</code> 组件提供的 <code>search</code> 组件实现结构</li></ol> <ul><li>分析 <code>search</code> 组件的结构并应用到页面中</li> <li>调整 <code>search</code> 组件的样式</li></ul> <div class="language-vue extra-class"><pre class="language-vue"><code><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>template</span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>div</span> <span class="token attr-name">class</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>search-container<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>
    <span class="token comment">&lt;!-- 在 van-search 外层增加 form 标签，且 action 不为空，即可在 iOS 输入法中显示搜索按钮。 --&gt;</span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>form</span> <span class="token attr-name">action</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>/<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>
      <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-search</span>
        <span class="token attr-name">v-model</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>searchText<span class="token punctuation">&quot;</span></span>
        <span class="token attr-name">show-action</span>
        <span class="token attr-name">placeholder</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>请输入搜索关键词<span class="token punctuation">&quot;</span></span>
        <span class="token attr-name">background</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>#3296fa<span class="token punctuation">&quot;</span></span>
        <span class="token attr-name">@search</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>onSearch<span class="token punctuation">&quot;</span></span>
        <span class="token attr-name">@cancel</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>onCancel<span class="token punctuation">&quot;</span></span>
      <span class="token punctuation">/&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>form</span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>div</span><span class="token punctuation">&gt;</span></span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>template</span><span class="token punctuation">&gt;</span></span>

<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>script</span><span class="token punctuation">&gt;</span></span><span class="token script"><span class="token language-javascript">
<span class="token keyword">export</span> <span class="token keyword">default</span> <span class="token punctuation">{</span>
  name<span class="token operator">:</span> <span class="token string">'SearchIndex'</span><span class="token punctuation">,</span>
  <span class="token function">data</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    <span class="token keyword">return</span> <span class="token punctuation">{</span>
      searchText<span class="token operator">:</span> <span class="token string">''</span>
    <span class="token punctuation">}</span>
  <span class="token punctuation">}</span><span class="token punctuation">,</span>
  methods<span class="token operator">:</span> <span class="token punctuation">{</span>
    <span class="token function">onSearch</span><span class="token punctuation">(</span><span class="token parameter">val</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
      console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>val<span class="token punctuation">)</span>
    <span class="token punctuation">}</span><span class="token punctuation">,</span>
    <span class="token function">onCancel</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
      <span class="token keyword">this</span><span class="token punctuation">.</span>$router<span class="token punctuation">.</span><span class="token function">back</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
    <span class="token punctuation">}</span>
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
</span></span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>script</span><span class="token punctuation">&gt;</span></span>

<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>style</span> <span class="token attr-name">scoped</span> <span class="token attr-name">lang</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>less<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span><span class="token style"><span class="token language-css">
<span class="token selector">.search-container</span> <span class="token punctuation">{</span>
  <span class="token selector">.van-search__action</span> <span class="token punctuation">{</span>
    <span class="token property">color</span><span class="token punctuation">:</span> #fff<span class="token punctuation">;</span>
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
</span></span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>style</span><span class="token punctuation">&gt;</span></span>

</code></pre></div><h4 id="_1-3-搜索区域的布局"><a href="#_1-3-搜索区域的布局" class="header-anchor">#</a> 1.3  搜索区域的布局</h4> <ol><li><p>实现<code>联想建议</code>、<code>历史记录</code>、<code>搜索结果</code> 3个区域实现布局，</p> <ul><li>我们采用父子组件的方式完成，拆分成 3 个组件</li> <li><code>search-history.vue</code>、<code>search-suggestion.vue</code>、<code>search-result.vue</code></li></ul></li> <li><p>分别创建 3 个组件并初始化基础结构</p></li></ol> <ul><li>创建 <code>\search\components\search-history.vue</code> 组件</li> <li>创建 <code>\search\components\search-suggestion.vue</code> 组件</li> <li>创建 <code>\search\components\search-result.vue</code> 组件</li></ul> <div class="language-vue extra-class"><pre class="language-vue"><code><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>template</span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>div</span><span class="token punctuation">&gt;</span></span>搜索历史<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>div</span><span class="token punctuation">&gt;</span></span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>template</span><span class="token punctuation">&gt;</span></span>

<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>script</span><span class="token punctuation">&gt;</span></span><span class="token script"><span class="token language-javascript">
<span class="token keyword">export</span> <span class="token keyword">default</span> <span class="token punctuation">{</span>
  name<span class="token operator">:</span> <span class="token string">'searchHistory'</span>
<span class="token punctuation">}</span>
</span></span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>script</span><span class="token punctuation">&gt;</span></span>

<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>style</span> <span class="token attr-name">lang</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>less<span class="token punctuation">&quot;</span></span> <span class="token attr-name">scoped</span><span class="token punctuation">&gt;</span></span><span class="token style"><span class="token language-css">
</span></span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>style</span><span class="token punctuation">&gt;</span></span>
</code></pre></div><div class="language-vue extra-class"><pre class="language-vue"><code><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>template</span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>div</span><span class="token punctuation">&gt;</span></span>搜索建议<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>div</span><span class="token punctuation">&gt;</span></span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>template</span><span class="token punctuation">&gt;</span></span>

<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>script</span><span class="token punctuation">&gt;</span></span><span class="token script"><span class="token language-javascript">
<span class="token keyword">export</span> <span class="token keyword">default</span> <span class="token punctuation">{</span>
  name<span class="token operator">:</span> <span class="token string">'searchSuggestion'</span>
<span class="token punctuation">}</span>
</span></span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>script</span><span class="token punctuation">&gt;</span></span>

<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>style</span> <span class="token attr-name">lang</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>less<span class="token punctuation">&quot;</span></span> <span class="token attr-name">scoped</span><span class="token punctuation">&gt;</span></span><span class="token style"><span class="token language-css">
</span></span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>style</span><span class="token punctuation">&gt;</span></span>
</code></pre></div><div class="language-vue extra-class"><pre class="language-vue"><code><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>template</span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>div</span><span class="token punctuation">&gt;</span></span>搜索结果<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>div</span><span class="token punctuation">&gt;</span></span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>template</span><span class="token punctuation">&gt;</span></span>

<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>script</span><span class="token punctuation">&gt;</span></span><span class="token script"><span class="token language-javascript">
<span class="token keyword">export</span> <span class="token keyword">default</span> <span class="token punctuation">{</span>
  name<span class="token operator">:</span> <span class="token string">'searchResult'</span>
<span class="token punctuation">}</span>
</span></span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>script</span><span class="token punctuation">&gt;</span></span>

<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>style</span> <span class="token attr-name">lang</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>less<span class="token punctuation">&quot;</span></span> <span class="token attr-name">scoped</span><span class="token punctuation">&gt;</span></span><span class="token style"><span class="token language-css">
</span></span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>style</span><span class="token punctuation">&gt;</span></span>
</code></pre></div><ol start="3"><li>将 3 个组件导入到搜索页面中</li></ol> <div class="language-js extra-class"><pre class="language-js"><code><span class="token operator">&lt;</span>script<span class="token operator">&gt;</span>
<span class="token keyword">import</span> searchHistory <span class="token keyword">from</span> <span class="token string">'./components/search-history.vue'</span>
<span class="token keyword">import</span> searchSuggestion <span class="token keyword">from</span> <span class="token string">'./components/search-suggestion.vue'</span>
<span class="token keyword">import</span> searchResult <span class="token keyword">from</span> <span class="token string">'./components/search-result.vue'</span>

<span class="token keyword">export</span> <span class="token keyword">default</span> <span class="token punctuation">{</span>
  components<span class="token operator">:</span> <span class="token punctuation">{</span>
    searchHistory<span class="token punctuation">,</span>
    searchSuggestion<span class="token punctuation">,</span>
    searchResult
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
<span class="token operator">&lt;</span><span class="token operator">/</span>script<span class="token operator">&gt;</span>
</code></pre></div><ol start="4"><li>实现 <code>search-history.vue</code> 组件布局</li></ol> <div class="language-vue extra-class"><pre class="language-vue"><code><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>template</span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>div</span> <span class="token attr-name">class</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>search-history<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-cell</span> <span class="token attr-name">title</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>搜索历史<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>
      <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>span</span><span class="token punctuation">&gt;</span></span>全部删除<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>span</span><span class="token punctuation">&gt;</span></span>
      <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>span</span><span class="token punctuation">&gt;</span></span>完成<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>span</span><span class="token punctuation">&gt;</span></span>
      <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-icon</span> <span class="token attr-name">name</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>delete<span class="token punctuation">&quot;</span></span> <span class="token punctuation">/&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>van-cell</span><span class="token punctuation">&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-cell</span> <span class="token attr-name">title</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>hello Tom<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>
      <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-icon</span> <span class="token attr-name">name</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>close<span class="token punctuation">&quot;</span></span> <span class="token punctuation">/&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>van-cell</span><span class="token punctuation">&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-cell</span> <span class="token attr-name">title</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>hello Tom<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>
      <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-icon</span> <span class="token attr-name">name</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>close<span class="token punctuation">&quot;</span></span> <span class="token punctuation">/&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>van-cell</span><span class="token punctuation">&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-cell</span> <span class="token attr-name">title</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>hello Tom<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>
      <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-icon</span> <span class="token attr-name">name</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>close<span class="token punctuation">&quot;</span></span> <span class="token punctuation">/&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>van-cell</span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>div</span><span class="token punctuation">&gt;</span></span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>template</span><span class="token punctuation">&gt;</span></span>

</code></pre></div><ol start="5"><li>实现 <code>search-suggest.vue</code> 组件布局</li></ol> <div class="language-vue extra-class"><pre class="language-vue"><code><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>template</span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>div</span> <span class="token attr-name">class</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>search-suggestion<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-cell</span> <span class="token attr-name">title</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>hello jerry<span class="token punctuation">&quot;</span></span> <span class="token attr-name">icon</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>search<span class="token punctuation">&quot;</span></span> <span class="token punctuation">/&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-cell</span> <span class="token attr-name">title</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>hello jerry<span class="token punctuation">&quot;</span></span> <span class="token attr-name">icon</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>search<span class="token punctuation">&quot;</span></span> <span class="token punctuation">/&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-cell</span> <span class="token attr-name">title</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>hello jerry<span class="token punctuation">&quot;</span></span> <span class="token attr-name">icon</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>search<span class="token punctuation">&quot;</span></span> <span class="token punctuation">/&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-cell</span> <span class="token attr-name">title</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>hello jerry<span class="token punctuation">&quot;</span></span> <span class="token attr-name">icon</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>search<span class="token punctuation">&quot;</span></span> <span class="token punctuation">/&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>div</span><span class="token punctuation">&gt;</span></span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>template</span><span class="token punctuation">&gt;</span></span>
</code></pre></div><ol start="6"><li>实现 <code>search-result.vue</code> 组件布局</li></ol> <div class="language-vue extra-class"><pre class="language-vue"><code><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>template</span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>div</span> <span class="token attr-name">class</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>search-result<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-list</span> <span class="token attr-name">v-model</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>loading<span class="token punctuation">&quot;</span></span> <span class="token attr-name">:finished</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>finished<span class="token punctuation">&quot;</span></span> <span class="token attr-name">finished-text</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>没有更多了<span class="token punctuation">&quot;</span></span> <span class="token attr-name">@load</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>onLoad<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>
      <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-cell</span> <span class="token attr-name">v-for</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>item in list<span class="token punctuation">&quot;</span></span> <span class="token attr-name">:key</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>item<span class="token punctuation">&quot;</span></span> <span class="token attr-name">:title</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>item<span class="token punctuation">&quot;</span></span> <span class="token punctuation">/&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>van-list</span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>div</span><span class="token punctuation">&gt;</span></span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>template</span><span class="token punctuation">&gt;</span></span>

<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>script</span><span class="token punctuation">&gt;</span></span><span class="token script"><span class="token language-javascript">
<span class="token keyword">export</span> <span class="token keyword">default</span> <span class="token punctuation">{</span>
  name<span class="token operator">:</span> <span class="token string">'searchResult'</span><span class="token punctuation">,</span>
  <span class="token function">data</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    <span class="token keyword">return</span> <span class="token punctuation">{</span>
      list<span class="token operator">:</span> <span class="token punctuation">[</span><span class="token punctuation">]</span><span class="token punctuation">,</span>
      loading<span class="token operator">:</span> <span class="token boolean">false</span><span class="token punctuation">,</span>
      finished<span class="token operator">:</span> <span class="token boolean">false</span>
    <span class="token punctuation">}</span>
  <span class="token punctuation">}</span><span class="token punctuation">,</span>
  methods<span class="token operator">:</span> <span class="token punctuation">{</span>
    <span class="token function">onLoad</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
      <span class="token comment">// 异步更新数据</span>
      <span class="token comment">// setTimeout 仅做示例，真实场景中一般为 ajax 请求</span>
      <span class="token function">setTimeout</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">=&gt;</span> <span class="token punctuation">{</span>
        <span class="token keyword">for</span> <span class="token punctuation">(</span><span class="token keyword">let</span> i <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span> i <span class="token operator">&lt;</span> <span class="token number">10</span><span class="token punctuation">;</span> i<span class="token operator">++</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
          <span class="token keyword">this</span><span class="token punctuation">.</span>list<span class="token punctuation">.</span><span class="token function">push</span><span class="token punctuation">(</span><span class="token keyword">this</span><span class="token punctuation">.</span>list<span class="token punctuation">.</span>length <span class="token operator">+</span> <span class="token number">1</span><span class="token punctuation">)</span>
        <span class="token punctuation">}</span>

        <span class="token comment">// 加载状态结束</span>
        <span class="token keyword">this</span><span class="token punctuation">.</span>loading <span class="token operator">=</span> <span class="token boolean">false</span>

        <span class="token comment">// 数据全部加载完成</span>
        <span class="token keyword">if</span> <span class="token punctuation">(</span><span class="token keyword">this</span><span class="token punctuation">.</span>list<span class="token punctuation">.</span>length <span class="token operator">&gt;=</span> <span class="token number">40</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
          <span class="token keyword">this</span><span class="token punctuation">.</span>finished <span class="token operator">=</span> <span class="token boolean">true</span>
        <span class="token punctuation">}</span>
      <span class="token punctuation">}</span><span class="token punctuation">,</span> <span class="token number">1000</span><span class="token punctuation">)</span>
    <span class="token punctuation">}</span>
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
</span></span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>script</span><span class="token punctuation">&gt;</span></span>

<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>style</span> <span class="token attr-name">lang</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>less<span class="token punctuation">&quot;</span></span> <span class="token attr-name">scoped</span><span class="token punctuation">&gt;</span></span><span class="token style"><span class="token language-css">
</span></span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>style</span><span class="token punctuation">&gt;</span></span>

</code></pre></div><h3 id="_2-处理-历史记录-联想建议-搜索结果-显示状态"><a href="#_2-处理-历史记录-联想建议-搜索结果-显示状态" class="header-anchor">#</a> 2. 处理(历史记录/联想建议/搜索结果)显示状态</h3> <ol><li><p>在 <code>data</code> 中添加数据用来控制搜索结果的显示状态</p> <div class="language-js extra-class"><pre class="language-js"><code><span class="token function">data</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">return</span> <span class="token punctuation">{</span>
    searchText<span class="token operator">:</span> <span class="token string">''</span><span class="token punctuation">,</span>
    isResultShow<span class="token operator">:</span> <span class="token boolean">false</span> <span class="token comment">// 控制搜索结果的显示状态</span>
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
</code></pre></div></li> <li><p>在模板中绑定条件渲染</p> <div class="language-vue extra-class"><pre class="language-vue"><code><span class="token comment">&lt;!-- 搜索结果 --&gt;</span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>search-result</span> <span class="token attr-name">v-if</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>isResultShow<span class="token punctuation">&quot;</span></span> <span class="token punctuation">/&gt;</span></span>
<span class="token comment">&lt;!-- 联想建议 --&gt;</span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>search-suggestiont&quot;</span> <span class="token punctuation">/&gt;</span></span>
<span class="token comment">&lt;!-- 搜索历史记录 --&gt;</span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>search-history</span> <span class="token attr-name">v-else</span> <span class="token punctuation">/&gt;</span></span>
</code></pre></div></li> <li><p>根据输入框 <code>searchText</code> 中有没有值，判断是否展示联想建议</p> <div class="language-vue extra-class"><pre class="language-vue"><code><span class="token comment">&lt;!-- 搜索结果 --&gt;</span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>search-result</span> <span class="token attr-name">v-if</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>isResultShow<span class="token punctuation">&quot;</span></span> <span class="token punctuation">/&gt;</span></span>
<span class="token comment">&lt;!-- 联想建议 --&gt;</span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>search-suggestion</span> <span class="token attr-name">v-else-if</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>searchText<span class="token punctuation">&quot;</span></span> <span class="token punctuation">/&gt;</span></span>
<span class="token comment">&lt;!-- 搜索历史记录 --&gt;</span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>search-history</span> <span class="token attr-name">v-else</span> <span class="token punctuation">/&gt;</span></span>
</code></pre></div></li> <li><p>在用户按回车以后，<code>onSearch</code> 事件中将 <code>isResultShow</code> 设置为 <code>true</code>，展示搜索结果组件</p></li></ol> <div class="language-js extra-class"><pre class="language-js"><code><span class="token function">onSearch</span><span class="token punctuation">(</span><span class="token parameter">val</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>val<span class="token punctuation">)</span>
  <span class="token keyword">this</span><span class="token punctuation">.</span>isResultShow <span class="token operator">=</span> <span class="token boolean">true</span>
<span class="token punctuation">}</span>
</code></pre></div><ol start="5"><li>再次在输入框输入内容以后发现不展示联想建议，这时候需要在输入框聚焦以后，将<code>isResultShow</code> 设置为 <code>false</code></li></ol> <div class="language-vue extra-class"><pre class="language-vue"><code><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-search</span>
  <span class="token attr-name">v-model</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>searchText<span class="token punctuation">&quot;</span></span>
  <span class="token attr-name">show-action</span>
  <span class="token attr-name">placeholder</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>请输入搜索关键词<span class="token punctuation">&quot;</span></span>
  <span class="token attr-name">background</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>#3296fa<span class="token punctuation">&quot;</span></span>
  <span class="token attr-name">@search</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>onSearch<span class="token punctuation">&quot;</span></span>
  <span class="token attr-name">@cancel</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>onCancel<span class="token punctuation">&quot;</span></span>
  <span class="token attr-name">@focus</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>isResultShow = false<span class="token punctuation">&quot;</span></span>
<span class="token punctuation">/&gt;</span></span>
</code></pre></div><ol start="6"><li>刷新页面，查看逻辑是否正确</li></ol> <hr> <h3 id="_3-搜索联想建议"><a href="#_3-搜索联想建议" class="header-anchor">#</a> 3. 搜索联想建议</h3> <h4 id="_3-1-实现思路"><a href="#_3-1-实现思路" class="header-anchor">#</a> 3.1 实现思路</h4> <ol><li>基本思路
<ul><li>当搜索框输入内容的时候，请求加载联想建议的数据</li> <li>将请求得到的结果绑定到模板中</li></ul></li> <li>基本功能</li></ol> <ul><li>将父组件中搜索框输入的内容传给联想建议子组件</li> <li>在子组件中监视搜索框输入内容的变化，如果变化则请求获取联想建议数据</li> <li>将获取到的联想建议数据展示到列表中</li></ul> <h4 id="_3-2-获取并监听输入框内容的变化"><a href="#_3-2-获取并监听输入框内容的变化" class="header-anchor">#</a> 3.2 获取并监听输入框内容的变化</h4> <ol><li>将搜索的关键字使用 <code>v-bind</code> 方式将值传入联想建议组件</li></ol> <div class="language-vue extra-class"><pre class="language-vue"><code><span class="token comment">&lt;!-- \views\search\index.vue --&gt;</span>

<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>search-suggestion</span> <span class="token attr-name">v-else-if</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>searchText<span class="token punctuation">&quot;</span></span> <span class="token attr-name">:search-text</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>searchText<span class="token punctuation">&quot;</span></span> <span class="token punctuation">/&gt;</span></span>
</code></pre></div><ol start="2"><li><p>在<code>\views\search\components\search-suggestion.vue</code> 组件接收值，并监听值的变化</p> <ul><li>使用 <code>props</code> 接收到返回的值</li> <li>使用 <code>watch</code> 监听值的变化</li></ul> <div class="language-js extra-class"><pre class="language-js"><code><span class="token operator">&lt;</span>script<span class="token operator">&gt;</span>
<span class="token keyword">export</span> <span class="token keyword">default</span> <span class="token punctuation">{</span>
  name<span class="token operator">:</span> <span class="token string">'searchSuggest'</span><span class="token punctuation">,</span>
  props<span class="token operator">:</span> <span class="token punctuation">{</span>
    searchText<span class="token operator">:</span> <span class="token punctuation">{</span>
      type<span class="token operator">:</span> String<span class="token punctuation">,</span>
      required<span class="token operator">:</span> <span class="token boolean">true</span>
    <span class="token punctuation">}</span>
  <span class="token punctuation">}</span><span class="token punctuation">,</span>
  watch<span class="token operator">:</span> <span class="token punctuation">{</span>
    searchText<span class="token operator">:</span> <span class="token punctuation">{</span>
      <span class="token comment">// 当 searchText 发生改变的时候就会调用 handler 方法</span>
      <span class="token function">handler</span> <span class="token punctuation">(</span><span class="token parameter">value</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
        console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>value<span class="token punctuation">)</span>
      <span class="token punctuation">}</span><span class="token punctuation">,</span>
      <span class="token comment">// 该回调将会在侦听开始以后被立即调用</span>
      immediate<span class="token operator">:</span> <span class="token boolean">true</span>
    <span class="token punctuation">}</span>
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
<span class="token operator">&lt;</span><span class="token operator">/</span>script<span class="token operator">&gt;</span>
</code></pre></div></li></ol> <h4 id="_3-3-请求获取展示数据"><a href="#_3-3-请求获取展示数据" class="header-anchor">#</a> 3.3 请求获取展示数据</h4> <ol><li><p>创建 <code>api/serach.js</code>，封装数据接口</p> <div class="language-js extra-class"><pre class="language-js"><code><span class="token comment">/**
 * 用户相关请求模块
 */</span>

<span class="token keyword">import</span> request <span class="token keyword">from</span> <span class="token string">'@/utils/request'</span>

<span class="token keyword">export</span> <span class="token keyword">const</span> <span class="token function-variable function">getSearchSuggestions</span> <span class="token operator">=</span> <span class="token parameter">q</span> <span class="token operator">=&gt;</span> <span class="token punctuation">{</span>
  <span class="token keyword">return</span> <span class="token function">request</span><span class="token punctuation">(</span><span class="token punctuation">{</span>
    method<span class="token operator">:</span> <span class="token string">'GET'</span><span class="token punctuation">,</span>
    url<span class="token operator">:</span> <span class="token string">'/app/v1_0/suggestion'</span><span class="token punctuation">,</span>
    params<span class="token operator">:</span> <span class="token punctuation">{</span>
      q
    <span class="token punctuation">}</span>
  <span class="token punctuation">}</span><span class="token punctuation">)</span>
<span class="token punctuation">}</span>
</code></pre></div></li> <li><p>在 <code>\views\search\components\search-suggestion.vue</code> 组件中导入 <code>getSearchSuggestions</code> 方法，并获取数据</p></li></ol> <ul><li>导入 <code>getSearchSuggestions</code> 方法</li> <li>声明 <code>loadSearchSuggestions</code> 方法获取数据</li> <li>在 <code>watch</code> 节点中的 <code>searchText</code> 方法调用获取数据的方法</li></ul> <div class="language-js extra-class"><pre class="language-js"><code><span class="token keyword">import</span> <span class="token punctuation">{</span> getSearchSuggestions <span class="token punctuation">}</span> <span class="token keyword">from</span> <span class="token string">'@/api/serach.js'</span>
</code></pre></div><div class="language-js extra-class"><pre class="language-js"><code><span class="token function">data</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  suggestions<span class="token operator">:</span> <span class="token punctuation">[</span><span class="token punctuation">]</span> <span class="token comment">// 联想建议数据列表</span>
<span class="token punctuation">}</span><span class="token punctuation">,</span>
methods<span class="token operator">:</span> <span class="token punctuation">{</span>
  <span class="token keyword">async</span> <span class="token function">loadSearchSuggestions</span> <span class="token punctuation">(</span><span class="token parameter">q</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    <span class="token keyword">try</span> <span class="token punctuation">{</span>
      <span class="token keyword">const</span> <span class="token punctuation">{</span> data <span class="token punctuation">}</span> <span class="token operator">=</span> <span class="token keyword">await</span> <span class="token function">getSearchSuggestions</span><span class="token punctuation">(</span>q<span class="token punctuation">)</span>
      <span class="token keyword">this</span><span class="token punctuation">.</span>suggestions <span class="token operator">=</span> data<span class="token punctuation">.</span>data<span class="token punctuation">.</span>options
    <span class="token punctuation">}</span> <span class="token keyword">catch</span> <span class="token punctuation">(</span>error<span class="token punctuation">)</span> <span class="token punctuation">{</span>
      <span class="token keyword">this</span><span class="token punctuation">.</span><span class="token function">$toast</span><span class="token punctuation">(</span><span class="token string">'获取数据失败, 请稍后重试'</span><span class="token punctuation">)</span>
    <span class="token punctuation">}</span>
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span><span class="token punctuation">,</span>
watch<span class="token operator">:</span> <span class="token punctuation">{</span>
  searchText<span class="token operator">:</span> <span class="token punctuation">{</span>
    <span class="token comment">// 当 searchText 发生改变的时候就会调用 handler 方法</span>
    <span class="token function">handler</span> <span class="token punctuation">(</span><span class="token parameter">value</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
      console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>value<span class="token punctuation">)</span>
      <span class="token keyword">this</span><span class="token punctuation">.</span><span class="token function">loadSearchSuggestions</span><span class="token punctuation">(</span>value<span class="token punctuation">)</span>
    <span class="token punctuation">}</span><span class="token punctuation">,</span>
    <span class="token comment">// 该回调将会在侦听开始以后被立即调用</span>
    immediate<span class="token operator">:</span> <span class="token boolean">true</span>
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
</code></pre></div><ol start="3"><li>使用请求到的数据获取页面</li></ol> <div class="language-vue extra-class"><pre class="language-vue"><code><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>template</span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>div</span> <span class="token attr-name">class</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>search-suggestion<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-cell</span> <span class="token attr-name">:title</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>text<span class="token punctuation">&quot;</span></span> <span class="token attr-name">icon</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>search<span class="token punctuation">&quot;</span></span> <span class="token attr-name">v-for</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>(text, index) in suggestions<span class="token punctuation">&quot;</span></span> <span class="token attr-name">:key</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>index<span class="token punctuation">&quot;</span></span> <span class="token punctuation">/&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>div</span><span class="token punctuation">&gt;</span></span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>template</span><span class="token punctuation">&gt;</span></span>
</code></pre></div><ol start="4"><li>刷新页面，输入内容，查看渲染结果是否成功</li></ol> <h4 id="_3-4-防抖处理"><a href="#_3-4-防抖处理" class="header-anchor">#</a> 3.4 防抖处理</h4> <blockquote><p>使用 <code>lodash</code> 提供的 <code>debounce</code> 函数解决抖动问题</p></blockquote> <ol><li><p>安装 <code>lodash</code></p> <div class="language-shell extra-class"><pre class="language-shell"><code><span class="token comment"># yarn add lodash</span>
<span class="token comment"># npm i lodash</span>

cnpm i lodash -S
</code></pre></div></li> <li><p>按需导入 <code>lodash</code> 提供的 <code>debounce</code> 函数</p></li></ol> <blockquote><p>不建议下面这样使用，因为这样会加载整个模块</p> <div class="language-js extra-class"><pre class="language-js"><code><span class="token keyword">import</span> _ <span class="token keyword">from</span> <span class="token string">'lodash'</span>
_<span class="token punctuation">.</span><span class="token function">debounce</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
</code></pre></div></blockquote> <div class="language-js extra-class"><pre class="language-js"><code><span class="token comment">// lodash 支持按需加载，有利于打包结果优化</span>

<span class="token keyword">import</span> <span class="token punctuation">{</span> debounce <span class="token punctuation">}</span> <span class="token keyword">from</span> <span class="token string">'lodash'</span>
</code></pre></div><ol start="3"><li>使用 <code>debounce</code> 函数</li></ol> <ul><li>参数 1：一个函数</li> <li>参数 2：延迟时间，单位是毫秒</li> <li>返回值：防抖之后的函数</li></ul> <div class="language-js extra-class"><pre class="language-js"><code>watch<span class="token operator">:</span> <span class="token punctuation">{</span>
  searchText<span class="token operator">:</span> <span class="token punctuation">{</span>
    handler<span class="token operator">:</span> <span class="token function">debounce</span><span class="token punctuation">(</span><span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token parameter">value</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
      <span class="token keyword">this</span><span class="token punctuation">.</span><span class="token function">loadSearchSuggestions</span><span class="token punctuation">(</span>value<span class="token punctuation">)</span>
    <span class="token punctuation">}</span><span class="token punctuation">,</span> <span class="token number">200</span><span class="token punctuation">)</span><span class="token punctuation">,</span>
    <span class="token comment">// 该回调将会在侦听开始以后被立即调用</span>
    immediate<span class="token operator">:</span> <span class="token boolean">true</span>
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
</code></pre></div><ol start="4"><li>刷新页面，打开控制台，查看是否还存在抖动问题</li></ol> <h4 id="_3-2-搜索关键字高亮"><a href="#_3-2-搜索关键字高亮" class="header-anchor">#</a> 3.2  搜索关键字高亮</h4> <h5 id="_3-2-1-思路分析"><a href="#_3-2-1-思路分析" class="header-anchor">#</a> 3.2.1 思路分析</h5> <ol><li><p>如何将字符串中的指定字符在<strong>网页</strong>中高亮展示？</p> <div class="language-html extra-class"><pre class="language-html"><code>&quot;Hello World&quot;;
</code></pre></div></li> <li><p>将需要高亮的字符包裹 <code>HTML</code> 标签，为其单独设置颜色</p></li></ol> <div class="language-html extra-class"><pre class="language-html"><code>&quot;Hello <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>span</span><span class="token style-attr language-css"><span class="token attr-name"> <span class="token attr-name">style</span></span><span class="token punctuation">=&quot;</span><span class="token attr-value"><span class="token property">color</span><span class="token punctuation">:</span> red</span><span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>World<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>span</span><span class="token punctuation">&gt;</span></span>&quot;
</code></pre></div><ol start="3"><li><p>在 <code>Vue</code> 中如何渲染带有 <code>HTML</code> 标签的字符串？</p> <div class="language-js extra-class"><pre class="language-js"><code><span class="token function">data</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">return</span> <span class="token punctuation">{</span>
    htmlStr<span class="token operator">:</span> <span class="token string">'Hello &lt;span style=&quot;color: red&quot;&gt;World&lt;/span&gt;'</span>
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
</code></pre></div><div class="language-vue extra-class"><pre class="language-vue"><code><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>div</span><span class="token punctuation">&gt;</span></span>{{ htmlStr }}<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>div</span><span class="token punctuation">&gt;</span></span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>div</span> <span class="token attr-name">v-html</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>htmlStr<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>div</span><span class="token punctuation">&gt;</span></span>
</code></pre></div><img src="/heima2020/assets/img/002 - 搜索关键字高亮.82578dc8.png" style="zoom:80%;"></li> <li><p>如何把字符串中指定字符统一替换为高亮（包裹了 HTML）的字符？</p></li></ol> <div class="language-js extra-class"><pre class="language-js"><code><span class="token keyword">const</span> str <span class="token operator">=</span> <span class="token string">&quot;Hello World&quot;</span>

<span class="token comment">// 结果：&lt;span style=&quot;color: red&quot;&gt;Hello&lt;/span&gt; World</span>
<span class="token string">&quot;Hello World&quot;</span><span class="token punctuation">.</span><span class="token function">replace</span><span class="token punctuation">(</span><span class="token string">'Hello'</span><span class="token punctuation">,</span> <span class="token string">'&lt;span style=&quot;color: red&quot;&gt;Hello&lt;/span&gt;'</span><span class="token punctuation">)</span>

<span class="token comment">// 需要注意的是，replace 方法的字符串匹配只能替换第1个满足的字符</span>
<span class="token comment">// &lt;span style=&quot;color: red&quot;&gt;Hello&lt;/span&gt; World Hello abc</span>
<span class="token string">&quot;Hello World Hello abc&quot;</span><span class="token punctuation">.</span><span class="token function">replace</span><span class="token punctuation">(</span><span class="token string">'Hello'</span><span class="token punctuation">,</span> <span class="token string">'&lt;span style=&quot;color: red&quot;&gt;Hello&lt;/span&gt;'</span><span class="token punctuation">)</span>

<span class="token comment">// 如果想要全文替换，使用正则表达式</span>
<span class="token comment">// g 全局</span>
<span class="token comment">// i 忽略大小写</span>
<span class="token comment">// &lt;span style=&quot;color: red&quot;&gt;Hello&lt;/span&gt; World &lt;span style=&quot;color: red&quot;&gt;Hello&lt;/span&gt; abc</span>
<span class="token string">&quot;Hello World Hello abc&quot;</span><span class="token punctuation">.</span><span class="token function">replace</span><span class="token punctuation">(</span><span class="token regex">/Hello/gi</span><span class="token punctuation">,</span> <span class="token string">'&lt;span style=&quot;color: red&quot;&gt;Hello&lt;/span&gt;'</span><span class="token punctuation">)</span>
</code></pre></div><ol start="5"><li><p>一个小扩展：使用字符串的 split 结合数组的 join 方法实现高亮</p> <div class="language-js extra-class"><pre class="language-js"><code><span class="token keyword">var</span> str <span class="token operator">=</span> <span class="token string">&quot;hello world 你好 hello&quot;</span><span class="token punctuation">;</span>

<span class="token comment">// [&quot;&quot;, &quot; world 你好 &quot;, &quot;&quot;]</span>
<span class="token keyword">const</span> arr <span class="token operator">=</span> str<span class="token punctuation">.</span><span class="token function">split</span><span class="token punctuation">(</span><span class="token string">&quot;hello&quot;</span><span class="token punctuation">)</span><span class="token punctuation">;</span>

<span class="token comment">// &quot;&lt;span&gt;hello&lt;/span&gt; world 你好 &lt;span&gt;hello&lt;/span&gt;&quot;</span>
arr<span class="token punctuation">.</span><span class="token function">join</span><span class="token punctuation">(</span><span class="token string">&quot;&lt;span&gt;hello&lt;/span&gt;&quot;</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
</code></pre></div></li></ol> <h5 id="_3-2-1-代码实现"><a href="#_3-2-1-代码实现" class="header-anchor">#</a> 3.2.1 代码实现</h5> <ol><li><p>在 <code>methods</code> 中添加一个方法处理高亮</p> <div class="language-js extra-class"><pre class="language-js"><code><span class="token function">highlight</span><span class="token punctuation">(</span><span class="token parameter">text</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">const</span> highlightStr <span class="token operator">=</span> <span class="token template-string"><span class="token template-punctuation string">`</span><span class="token string">&lt;span class=&quot;active&quot;&gt;</span><span class="token interpolation"><span class="token interpolation-punctuation punctuation">${</span><span class="token keyword">this</span><span class="token punctuation">.</span>searchText<span class="token interpolation-punctuation punctuation">}</span></span><span class="token string">&lt;/span&gt;</span><span class="token template-punctuation string">`</span></span>
  <span class="token comment">// 正则表达式 // 中间的内容都会被当作匹配字符串来使用，而不是数据变量</span>
  <span class="token comment">// 如果需要根据数据变量动态的创建正则表达式，则手动 new RegExp</span>
  <span class="token comment">// RegExp 正则表达式构造函数</span>
  <span class="token comment">// 参数 1： 匹配模式字符串，它会根据这个字符串创建正则对象</span>
  <span class="token comment">// 参数 2： 匹配模式，要写到字符串中</span>

  <span class="token keyword">const</span> reg <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">RegExp</span><span class="token punctuation">(</span><span class="token keyword">this</span><span class="token punctuation">.</span>searchText<span class="token punctuation">,</span> <span class="token string">'gi'</span><span class="token punctuation">)</span>
  <span class="token keyword">return</span> text<span class="token punctuation">.</span><span class="token function">replace</span><span class="token punctuation">(</span>reg<span class="token punctuation">,</span> highlightStr<span class="token punctuation">)</span>
<span class="token punctuation">}</span>
</code></pre></div></li> <li><p>在联想建议列表项中绑定调用</p> <div class="language-vue extra-class"><pre class="language-vue"><code><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>template</span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>div</span> <span class="token attr-name">class</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>search-suggestion<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-cell</span> <span class="token attr-name">icon</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>search<span class="token punctuation">&quot;</span></span> <span class="token attr-name">v-for</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>(text, index) in suggestions<span class="token punctuation">&quot;</span></span> <span class="token attr-name">:key</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>index<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>
      <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>div</span> <span class="token attr-name">slot</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>title<span class="token punctuation">&quot;</span></span> <span class="token attr-name">v-html</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>highlight(text)<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>div</span><span class="token punctuation">&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>van-cell</span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>div</span><span class="token punctuation">&gt;</span></span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>template</span><span class="token punctuation">&gt;</span></span>
</code></pre></div></li> <li><p>刷新页面，在输入框输入内容，查看显示的搜索建议是否高亮</p></li></ol> <h3 id="_4-搜索结果"><a href="#_4-搜索结果" class="header-anchor">#</a> 4. 搜索结果</h3> <h4 id="_4-1-传递搜索内容到父级"><a href="#_4-1-传递搜索内容到父级" class="header-anchor">#</a> 4.1 传递搜索内容到父级</h4> <blockquote><p>点击搜索建议的内容，将内容传递到父级，并在输入框展示，</p> <p>这里涉及到父子组件传值，所有还是使用 <code>$emit</code> 以及 <code>$on</code> 的方式处理数据</p></blockquote> <ol><li>给搜索建议列表绑定点击事件，并使用 <code>$emit</code> 将值传递给父级</li></ol> <div class="language-vue extra-class"><pre class="language-vue"><code><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-cell</span>
  <span class="token attr-name">icon</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>search<span class="token punctuation">&quot;</span></span>
  <span class="token attr-name">v-for</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>(text, index) in suggestions<span class="token punctuation">&quot;</span></span>
  <span class="token attr-name">:key</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>index<span class="token punctuation">&quot;</span></span>
  <span class="token attr-name">@click</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>$emit(<span class="token punctuation">'</span>search<span class="token punctuation">'</span>, text)<span class="token punctuation">&quot;</span></span>
<span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>div</span> <span class="token attr-name">slot</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>title<span class="token punctuation">&quot;</span></span> <span class="token attr-name">v-html</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>highlight(text)<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>div</span><span class="token punctuation">&gt;</span></span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>van-cell</span><span class="token punctuation">&gt;</span></span>
</code></pre></div><ol start="2"><li>父组件中使用 <code>$on</code> 接收到传递的值</li></ol> <div class="language-vue extra-class"><pre class="language-vue"><code><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>search-suggestion</span> <span class="token attr-name">@search</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>onSearch<span class="token punctuation">&quot;</span></span> <span class="token attr-name">v-else-if</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>searchText<span class="token punctuation">&quot;</span></span> <span class="token attr-name">:search-text</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>searchText<span class="token punctuation">&quot;</span></span> <span class="token punctuation">/&gt;</span></span>
</code></pre></div><ol start="3"><li>在事件处理程序中， 将值并在输入框展示</li></ol> <div class="language-js extra-class"><pre class="language-js"><code><span class="token function">onSearch</span><span class="token punctuation">(</span><span class="token parameter">val</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">this</span><span class="token punctuation">.</span>searchText <span class="token operator">=</span> val
  <span class="token keyword">this</span><span class="token punctuation">.</span>isResultShow <span class="token operator">=</span> <span class="token boolean">true</span>
<span class="token punctuation">}</span>
</code></pre></div><ol start="4"><li>将值传递给 <code>search-result</code> 组件</li></ol> <div class="language-vue extra-class"><pre class="language-vue"><code> <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>search-result</span> <span class="token attr-name">v-if</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>isResultShow<span class="token punctuation">&quot;</span></span> <span class="token attr-name">:search-text</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>searchText<span class="token punctuation">&quot;</span></span> <span class="token punctuation">/&gt;</span></span>
</code></pre></div><ol start="5"><li><p>在 <code>search-result</code> 组件中使用 <code>props</code> 接收到传递的值</p> <div class="language-js extra-class"><pre class="language-js"><code><span class="token operator">&lt;</span>script<span class="token operator">&gt;</span>
<span class="token keyword">export</span> <span class="token keyword">default</span> <span class="token punctuation">{</span>
  name<span class="token operator">:</span> <span class="token string">'searchHistory'</span><span class="token punctuation">,</span>
  props<span class="token operator">:</span> <span class="token punctuation">{</span>
    searchText<span class="token operator">:</span> <span class="token punctuation">{</span>
      type<span class="token operator">:</span> String<span class="token punctuation">,</span>
      required<span class="token operator">:</span> <span class="token boolean">true</span>
    <span class="token punctuation">}</span>
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
<span class="token operator">&lt;</span><span class="token operator">/</span>script<span class="token operator">&gt;</span>
</code></pre></div></li> <li><p>刷新页面，在输入框输入内容，点击建议列表后者回车，查看是否实现传值</p></li></ol> <h4 id="_4-2-处理搜索结果"><a href="#_4-2-处理搜索结果" class="header-anchor">#</a> 4.2 处理搜索结果</h4> <ol><li>在 <code>src\api\serach.js</code> 中封装接口请求函数</li></ol> <div class="language-js extra-class"><pre class="language-js"><code><span class="token comment">// 获取搜索结果</span>
<span class="token keyword">export</span> <span class="token keyword">const</span> <span class="token function-variable function">getSearchResult</span> <span class="token operator">=</span> <span class="token parameter">params</span> <span class="token operator">=&gt;</span> <span class="token punctuation">{</span>
  <span class="token keyword">return</span> <span class="token function">request</span><span class="token punctuation">(</span><span class="token punctuation">{</span>
    method<span class="token operator">:</span> <span class="token string">'GET'</span><span class="token punctuation">,</span>
    url<span class="token operator">:</span> <span class="token string">'/app/v1_0/search'</span><span class="token punctuation">,</span>
    params
  <span class="token punctuation">}</span><span class="token punctuation">)</span>
<span class="token punctuation">}</span>
</code></pre></div><ol start="2"><li>在 <code>\views\search\components\search-result.vue</code> 方法中导入 <code>getSearchResult</code> 方法，获取搜索结果数据</li></ol> <ul><li>导入 <code>getSearchResult</code> 方法</li> <li>在 <code>onLoad</code> 方法中处理业务逻辑</li></ul> <div class="language-js extra-class"><pre class="language-js"><code><span class="token operator">&lt;</span>script<span class="token operator">&gt;</span>
<span class="token keyword">import</span> <span class="token punctuation">{</span> getSearchResult <span class="token punctuation">}</span> <span class="token keyword">from</span> <span class="token string">'@/api/serach.js'</span>
<span class="token keyword">export</span> <span class="token keyword">default</span> <span class="token punctuation">{</span>
  name<span class="token operator">:</span> <span class="token string">'searchResult'</span><span class="token punctuation">,</span>
  props<span class="token operator">:</span> <span class="token punctuation">{</span>
    searchText<span class="token operator">:</span> <span class="token punctuation">{</span>
      type<span class="token operator">:</span> String<span class="token punctuation">,</span>
      required<span class="token operator">:</span> <span class="token boolean">true</span>
    <span class="token punctuation">}</span>
  <span class="token punctuation">}</span><span class="token punctuation">,</span>
  <span class="token function">data</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    <span class="token keyword">return</span> <span class="token punctuation">{</span>
      list<span class="token operator">:</span> <span class="token punctuation">[</span><span class="token punctuation">]</span><span class="token punctuation">,</span>
      loading<span class="token operator">:</span> <span class="token boolean">false</span><span class="token punctuation">,</span>
      finished<span class="token operator">:</span> <span class="token boolean">false</span><span class="token punctuation">,</span>
      page<span class="token operator">:</span> <span class="token number">1</span><span class="token punctuation">,</span>
      perPage<span class="token operator">:</span> <span class="token number">20</span>
    <span class="token punctuation">}</span>
  <span class="token punctuation">}</span><span class="token punctuation">,</span>
  methods<span class="token operator">:</span> <span class="token punctuation">{</span>
    <span class="token keyword">async</span> <span class="token function">onLoad</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
      <span class="token keyword">try</span> <span class="token punctuation">{</span>
        <span class="token comment">// 1. 请求获取数据</span>
        <span class="token keyword">const</span> <span class="token punctuation">{</span> data <span class="token punctuation">}</span> <span class="token operator">=</span> <span class="token keyword">await</span> <span class="token function">getSearchResult</span><span class="token punctuation">(</span><span class="token punctuation">{</span>
          page<span class="token operator">:</span> <span class="token keyword">this</span><span class="token punctuation">.</span>page<span class="token punctuation">,</span> <span class="token comment">// 页码</span>
          per_page<span class="token operator">:</span> <span class="token keyword">this</span><span class="token punctuation">.</span>perPage<span class="token punctuation">,</span> <span class="token comment">// 每页大小</span>
          q<span class="token operator">:</span> <span class="token keyword">this</span><span class="token punctuation">.</span>searchText <span class="token comment">// 搜索关键字</span>
        <span class="token punctuation">}</span><span class="token punctuation">)</span>

        <span class="token comment">// 2. 将数据添加到列表中</span>
        <span class="token keyword">const</span> <span class="token punctuation">{</span> results <span class="token punctuation">}</span> <span class="token operator">=</span> data<span class="token punctuation">.</span>data
        <span class="token keyword">this</span><span class="token punctuation">.</span>list<span class="token punctuation">.</span><span class="token function">push</span><span class="token punctuation">(</span><span class="token operator">...</span>results<span class="token punctuation">)</span>
        console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token keyword">this</span><span class="token punctuation">.</span>list<span class="token punctuation">)</span>

        <span class="token comment">// 3. 设置加载状态结束</span>
        <span class="token keyword">this</span><span class="token punctuation">.</span>loading <span class="token operator">=</span> <span class="token boolean">false</span>

        <span class="token comment">// 4. 判断数据是否加载完毕</span>
        <span class="token keyword">if</span> <span class="token punctuation">(</span>results<span class="token punctuation">.</span>length<span class="token punctuation">)</span> <span class="token punctuation">{</span>
          <span class="token keyword">this</span><span class="token punctuation">.</span>page<span class="token operator">++</span> <span class="token comment">// 更新获取下一页数据的页码</span>
       ad
        <span class="token punctuation">}</span>
      <span class="token punctuation">}</span> <span class="token keyword">catch</span> <span class="token punctuation">(</span>error<span class="token punctuation">)</span> <span class="token punctuation">{</span>
        <span class="token keyword">this</span><span class="token punctuation">.</span><span class="token function">$toast</span><span class="token punctuation">(</span><span class="token string">'数据获取失败, 请稍后再试'</span><span class="token punctuation">)</span>
      <span class="token punctuation">}</span>
    <span class="token punctuation">}</span>
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
<span class="token operator">&lt;</span><span class="token operator">/</span>script<span class="token operator">&gt;</span>
</code></pre></div><ol start="3"><li><p>使用数据渲染页面</p> <div class="language-vue extra-class"><pre class="language-vue"><code><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>template</span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>div</span> <span class="token attr-name">class</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>search-result<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-list</span> <span class="token attr-name">v-model</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>loading<span class="token punctuation">&quot;</span></span> <span class="token attr-name">:finished</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>finished<span class="token punctuation">&quot;</span></span> <span class="token attr-name">finished-text</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>没有更多了<span class="token punctuation">&quot;</span></span> <span class="token attr-name">@load</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>onLoad<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>
      <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-cell</span> <span class="token attr-name">v-for</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>(article, index) in list<span class="token punctuation">&quot;</span></span> <span class="token attr-name">:key</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>index<span class="token punctuation">&quot;</span></span> <span class="token attr-name">:title</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>article.title<span class="token punctuation">&quot;</span></span> <span class="token punctuation">/&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>van-list</span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>div</span><span class="token punctuation">&gt;</span></span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>template</span><span class="token punctuation">&gt;</span></span>
</code></pre></div></li> <li><p>给代码进行优化，加上错误提示</p> <div class="language-vue extra-class"><pre class="language-vue"><code><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-list</span>
  <span class="token attr-name">v-model</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>loading<span class="token punctuation">&quot;</span></span>
  <span class="token attr-name">:finished</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>finished<span class="token punctuation">&quot;</span></span>
  <span class="token attr-name">:error</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>error<span class="token punctuation">&quot;</span></span>
  <span class="token attr-name">error-text</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>加载失败，请点击重试<span class="token punctuation">&quot;</span></span>
  <span class="token attr-name">finished-text</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>没有更多了<span class="token punctuation">&quot;</span></span>
  <span class="token attr-name">@load</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>onLoad<span class="token punctuation">&quot;</span></span>
<span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-cell</span> <span class="token attr-name">v-for</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>(article, index) in list<span class="token punctuation">&quot;</span></span> <span class="token attr-name">:key</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>index<span class="token punctuation">&quot;</span></span> <span class="token attr-name">:title</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>article.title<span class="token punctuation">&quot;</span></span> <span class="token punctuation">/&gt;</span></span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>van-list</span><span class="token punctuation">&gt;</span></span>
</code></pre></div><div class="language-js extra-class"><pre class="language-js"><code><span class="token function">data</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">return</span> <span class="token punctuation">{</span>
    error<span class="token operator">:</span> <span class="token boolean">false</span>
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
</code></pre></div><div class="language-js extra-class"><pre class="language-js"><code><span class="token keyword">async</span> <span class="token function">onLoad</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">try</span> <span class="token punctuation">{</span>
      
    <span class="token comment">// coding……略</span>
      
  <span class="token punctuation">}</span> <span class="token keyword">catch</span> <span class="token punctuation">(</span>error<span class="token punctuation">)</span> <span class="token punctuation">{</span>
    <span class="token comment">// 展示加载失败的提示状态</span>
    <span class="token keyword">this</span><span class="token punctuation">.</span>error <span class="token operator">=</span> <span class="token boolean">true</span>
    <span class="token comment">// 加载失败了. loading 也要关闭</span>
    <span class="token keyword">this</span><span class="token punctuation">.</span>loading <span class="token operator">=</span> <span class="token boolean">false</span>
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
</code></pre></div></li> <li><p>设置搜索框悬浮效果</p> <div class="language-vue extra-class"><pre class="language-vue"><code><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>form</span> <span class="token attr-name">action</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>/<span class="token punctuation">&quot;</span></span> <span class="token attr-name">class</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>search-form<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>
  // coding……略
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>form</span><span class="token punctuation">&gt;</span></span>
</code></pre></div><div class="language-less extra-class"><pre class="language-less"><code><span class="token selector">&lt;style scoped lang=&quot;less&quot;&gt;
.search-container</span> <span class="token punctuation">{</span>
  <span class="token property">padding-top</span><span class="token punctuation">:</span> 108px<span class="token punctuation">;</span>

  <span class="token selector">.van-search__action</span> <span class="token punctuation">{</span>
    <span class="token property">color</span><span class="token punctuation">:</span> #fff<span class="token punctuation">;</span>
  <span class="token punctuation">}</span>

  <span class="token selector">.search-form</span> <span class="token punctuation">{</span>
    <span class="token property">position</span><span class="token punctuation">:</span> fixed<span class="token punctuation">;</span>
    <span class="token property">top</span><span class="token punctuation">:</span> 0<span class="token punctuation">;</span>
    <span class="token property">left</span><span class="token punctuation">:</span> 0<span class="token punctuation">;</span>
    <span class="token property">right</span><span class="token punctuation">:</span> 0<span class="token punctuation">;</span>
    <span class="token property">z-index</span><span class="token punctuation">:</span> 1<span class="token punctuation">;</span>
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
&lt;<span class="token operator">/</span>style&gt;
</code></pre></div></li> <li><p>刷新页面，在输入框输入内容，点击建议列表或者回车，查看搜索结果页是否渲染成功</p></li></ol> <hr> <h3 id="_5-搜索历史记录"><a href="#_5-搜索历史记录" class="header-anchor">#</a> 5. 搜索历史记录</h3> <h4 id="_5-1-添加历史记录"><a href="#_5-1-添加历史记录" class="header-anchor">#</a> 5. 1 添加历史记录</h4> <blockquote><p>当发生搜索的时候我们才需要记录历史记录</p></blockquote> <ol><li><p>在 data 中添加一个数据用来存储历史记录</p> <div class="language-js extra-class"><pre class="language-js"><code><span class="token function">data</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">return</span> <span class="token punctuation">{</span>
    searchHistories<span class="token operator">:</span> <span class="token punctuation">[</span><span class="token punctuation">]</span> <span class="token comment">// 存储历史记录</span>
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
</code></pre></div></li> <li><p>在触发搜索的时候，记录历史记录</p> <div class="language-js extra-class"><pre class="language-js"><code><span class="token comment">// 确定搜索时触发</span>
<span class="token function">onSearch</span><span class="token punctuation">(</span><span class="token parameter">val</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token comment">// 更新文本框的内容</span>
  <span class="token keyword">this</span><span class="token punctuation">.</span>searchText <span class="token operator">=</span> val

  <span class="token comment">// 存储搜索历史记录</span>
  <span class="token comment">// 不要有重复历史记录、最新的排在最前面</span>
  <span class="token keyword">const</span> index <span class="token operator">=</span> <span class="token keyword">this</span><span class="token punctuation">.</span>searchHistories<span class="token punctuation">.</span><span class="token function">indexOf</span><span class="token punctuation">(</span>val<span class="token punctuation">)</span>
  <span class="token keyword">if</span> <span class="token punctuation">(</span>index <span class="token operator">!==</span> <span class="token operator">-</span><span class="token number">1</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    <span class="token keyword">this</span><span class="token punctuation">.</span>searchHistories<span class="token punctuation">.</span><span class="token function">splice</span><span class="token punctuation">(</span>index<span class="token punctuation">,</span> <span class="token number">1</span><span class="token punctuation">)</span>
  <span class="token punctuation">}</span>

  <span class="token keyword">this</span><span class="token punctuation">.</span>searchHistories<span class="token punctuation">.</span><span class="token function">unshift</span><span class="token punctuation">(</span>val<span class="token punctuation">)</span>

  <span class="token comment">// 渲染搜索结果</span>
  <span class="token keyword">this</span><span class="token punctuation">.</span>isResultShow <span class="token operator">=</span> <span class="token boolean">true</span>
<span class="token punctuation">}</span>
</code></pre></div></li> <li><p>刷新页面，打开 <code>Vue devTools</code> 查看是否传值成功</p></li></ol> <h4 id="_5-2-展示历史记录"><a href="#_5-2-展示历史记录" class="header-anchor">#</a> 5. 2 展示历史记录</h4> <ol><li>将搜索历史记录传递给子组件</li></ol> <div class="language-vue extra-class"><pre class="language-vue"><code><span class="token comment">&lt;!-- 搜索历史记录 --&gt;</span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>search-history</span> <span class="token attr-name">v-else</span> <span class="token attr-name">:search-histories</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>searchHistories<span class="token punctuation">&quot;</span></span> <span class="token punctuation">/&gt;</span></span>
</code></pre></div><ol start="2"><li><p>子组件中使用 <code>props</code> 接收父组件传递的数据</p> <div class="language-js extra-class"><pre class="language-js"><code><span class="token keyword">export</span> <span class="token keyword">default</span> <span class="token punctuation">{</span>
  name<span class="token operator">:</span> <span class="token string">'searchHistory'</span><span class="token punctuation">,</span>
  props<span class="token operator">:</span> <span class="token punctuation">{</span>
    searchHistories<span class="token operator">:</span> <span class="token punctuation">{</span>
      type<span class="token operator">:</span> Array<span class="token punctuation">,</span>
      required<span class="token operator">:</span> <span class="token boolean">true</span>
    <span class="token punctuation">}</span>
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
</code></pre></div></li> <li><p>渲染父组件传递的历史记录数据</p> <div class="language-vue extra-class"><pre class="language-vue"><code><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-cell</span> <span class="token attr-name">v-for</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>(item, index) in searchHistories<span class="token punctuation">&quot;</span></span> <span class="token attr-name">:key</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>index<span class="token punctuation">&quot;</span></span> <span class="token attr-name">:title</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>item<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-icon</span> <span class="token attr-name">name</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>close<span class="token punctuation">&quot;</span></span> <span class="token punctuation">/&gt;</span></span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>van-cell</span><span class="token punctuation">&gt;</span></span>
</code></pre></div></li> <li><p>刷新页面，在输入框输入内容，查看历史记录是否渲染成功</p></li></ol> <h4 id="_5-3-处理删除显示状态"><a href="#_5-3-处理删除显示状态" class="header-anchor">#</a> 5.3 处理删除显示状态</h4> <ol><li>在 <code>data</code> 中添加一个数据用来控制删除相关元素的显示状态</li></ol> <div class="language-js extra-class"><pre class="language-js"><code><span class="token function">data</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">return</span> <span class="token punctuation">{</span>
    isDeleteShow<span class="token operator">:</span> <span class="token boolean">false</span> <span class="token comment">// 控制删除显示状态</span>
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
</code></pre></div><ol start="2"><li><p>在页面中绑定属性，控制元素的显示与否</p> <div class="language-vue extra-class"><pre class="language-vue"><code><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>template</span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>div</span> <span class="token attr-name">class</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>search-history<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-cell</span> <span class="token attr-name">title</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>搜索历史<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>
      <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>div</span> <span class="token attr-name">v-if</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>isDeleteShow<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>
        <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>span</span><span class="token punctuation">&gt;</span></span>全部删除<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>span</span><span class="token punctuation">&gt;</span></span><span class="token entity named-entity" title="&amp;nbsp;">&amp;nbsp;</span><span class="token entity named-entity" title="&amp;nbsp;">&amp;nbsp;</span><span class="token entity named-entity" title="&amp;nbsp;">&amp;nbsp;</span><span class="token entity named-entity" title="&amp;nbsp;">&amp;nbsp;</span>
        <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>span</span> <span class="token attr-name">@click</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>isDeleteShow = false<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>完成<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>span</span><span class="token punctuation">&gt;</span></span>
      <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>div</span><span class="token punctuation">&gt;</span></span>
      <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-icon</span> <span class="token attr-name">v-else</span> <span class="token attr-name">name</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>delete<span class="token punctuation">&quot;</span></span> <span class="token attr-name">@click</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>isDeleteShow = true<span class="token punctuation">&quot;</span></span> <span class="token punctuation">/&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>van-cell</span><span class="token punctuation">&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-cell</span> <span class="token attr-name">v-for</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>(item, index) in searchHistories<span class="token punctuation">&quot;</span></span> <span class="token attr-name">:key</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>index<span class="token punctuation">&quot;</span></span> <span class="token attr-name">:title</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>item<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>
      <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-icon</span> <span class="token attr-name">v-if</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>isDeleteShow<span class="token punctuation">&quot;</span></span> <span class="token attr-name">name</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>close<span class="token punctuation">&quot;</span></span> <span class="token punctuation">/&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>van-cell</span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>div</span><span class="token punctuation">&gt;</span></span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>template</span><span class="token punctuation">&gt;</span></span>
</code></pre></div></li></ol> <h4 id="_5-4-处理删除逻辑"><a href="#_5-4-处理删除逻辑" class="header-anchor">#</a> 5. 4 处理删除逻辑</h4> <ol><li><p>给每一条历史记录绑定点击事件</p> <div class="language-vue extra-class"><pre class="language-vue"><code><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-cell</span>
  <span class="token attr-name">v-for</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>(item, index) in searchHistories<span class="token punctuation">&quot;</span></span>
  <span class="token attr-name">:key</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>index<span class="token punctuation">&quot;</span></span>
  <span class="token attr-name">:title</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>item<span class="token punctuation">&quot;</span></span>
  <span class="token attr-name">@click</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>onSearchItemClick(item, index)<span class="token punctuation">&quot;</span></span>
<span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>van-icon</span> <span class="token attr-name">v-if</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>isDeleteShow<span class="token punctuation">&quot;</span></span> <span class="token attr-name">name</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>close<span class="token punctuation">&quot;</span></span> <span class="token punctuation">/&gt;</span></span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>van-cell</span><span class="token punctuation">&gt;</span></span>
</code></pre></div></li> <li><p>在事件处理程序中，接收到传递的历史项以及历史项索引，根据索引删除数组中的数据</p> <div class="language-js extra-class"><pre class="language-js"><code><span class="token comment">// 删除项点击操作</span>
<span class="token function">onSearchItemClick</span> <span class="token punctuation">(</span><span class="token parameter">item<span class="token punctuation">,</span> index</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">if</span> <span class="token punctuation">(</span><span class="token keyword">this</span><span class="token punctuation">.</span>isDeleteShow<span class="token punctuation">)</span> <span class="token punctuation">{</span>
    <span class="token comment">// 删除状态，删除历史记录数据</span>
    <span class="token keyword">this</span><span class="token punctuation">.</span>searchHistories<span class="token punctuation">.</span><span class="token function">splice</span><span class="token punctuation">(</span>index<span class="token punctuation">,</span> <span class="token number">1</span><span class="token punctuation">)</span>
  <span class="token punctuation">}</span> <span class="token keyword">else</span> <span class="token punctuation">{</span>
    <span class="token comment">// 非删除状态，直接进入搜索</span>
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
</code></pre></div></li> <li><p>点击全部删除，这个删除，我们不能直接 <code>props</code> 中的 <code>searchHistories</code> ，需要使用 <code>$emit</code> 交给父级进行处理</p> <ul><li><code>props</code> 是受组件数据影响的</li> <li>如果是普通数据(数字、字符串、布尔值)，绝对不能修改，即使改了也不会传导给父组件</li> <li>如果是引用类型(数组、对象)，可以修改，但是不能够直接赋值</li></ul> <div class="language-vue extra-class"><pre class="language-vue"><code><span class="token comment">&lt;!-- search-history.vue --&gt;</span>

<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>span</span> <span class="token attr-name">@click</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>$emit(<span class="token punctuation">'</span>clear-search-histories<span class="token punctuation">'</span>)<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>全部删除<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>span</span><span class="token punctuation">&gt;</span></span>
</code></pre></div><div class="language-vue extra-class"><pre class="language-vue"><code><span class="token comment">&lt;!-- index.vue --&gt;</span>

<span class="token comment">&lt;!-- 搜索历史记录 --&gt;</span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>search-history</span>
  <span class="token attr-name">v-else</span>
  <span class="token attr-name">:search-histories</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>searchHistories<span class="token punctuation">&quot;</span></span>
  <span class="token attr-name">@clear-search-histories</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>searchHistories = []<span class="token punctuation">&quot;</span></span>
<span class="token punctuation">/&gt;</span></span>
</code></pre></div></li> <li><p>如果点击的不是删除，那么删除也需要传递到父组件中进行搜索，所以这里使用的还是  <code>$emit</code> 方法传递给父级处理</p> <ul><li>传递给父级中，触发父组件中的 <code>onSearch</code> 方法</li> <li><code>onSearch</code> 方法接收到传递的数据，执行搜索的操作</li></ul> <div class="language-js extra-class"><pre class="language-js"><code><span class="token comment">// 删除项点击操作</span>
<span class="token function">onSearchItemClick</span> <span class="token punctuation">(</span><span class="token parameter">item<span class="token punctuation">,</span> index</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">if</span> <span class="token punctuation">(</span><span class="token keyword">this</span><span class="token punctuation">.</span>isDeleteShow<span class="token punctuation">)</span> <span class="token punctuation">{</span>
    <span class="token comment">// 删除状态，删除历史记录数据</span>
    <span class="token keyword">this</span><span class="token punctuation">.</span>searchHistories<span class="token punctuation">.</span><span class="token function">splice</span><span class="token punctuation">(</span>index<span class="token punctuation">,</span> <span class="token number">1</span><span class="token punctuation">)</span>
  <span class="token punctuation">}</span> <span class="token keyword">else</span> <span class="token punctuation">{</span>
    <span class="token comment">// 非删除状态，直接进入搜索</span>
    <span class="token keyword">this</span><span class="token punctuation">.</span><span class="token function">$emit</span><span class="token punctuation">(</span><span class="token string">'search'</span><span class="token punctuation">,</span> item<span class="token punctuation">)</span>
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
</code></pre></div><div class="language-vue extra-class"><pre class="language-vue"><code><span class="token comment">&lt;!-- index.vue --&gt;</span>

<span class="token comment">&lt;!-- 搜索历史记录 --&gt;</span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>search-history</span>
  <span class="token attr-name">v-else</span>
  <span class="token attr-name">:search-histories</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>searchHistories<span class="token punctuation">&quot;</span></span>
  <span class="token attr-name">@clear-search-histories</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>searchHistories = []<span class="token punctuation">&quot;</span></span>
  <span class="token attr-name">@search</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>onSearch<span class="token punctuation">&quot;</span></span>
<span class="token punctuation">/&gt;</span></span>
</code></pre></div></li> <li><p>刷线页面，测试逻辑功能是否实现</p></li></ol> <h4 id="_5-5-数据持久化"><a href="#_5-5-数据持久化" class="header-anchor">#</a> 5. 5 数据持久化</h4> <ol><li><p>利用 watch 监视统一存储数据</p> <div class="language-js extra-class"><pre class="language-js"><code>watch<span class="token operator">:</span> <span class="token punctuation">{</span>
  <span class="token function">searchHistories</span> <span class="token punctuation">(</span><span class="token parameter">value</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    <span class="token comment">// 同步搜索数据到本地</span>
    <span class="token function">setItem</span><span class="token punctuation">(</span><span class="token string">'TOUTIAO_SEARCH_HISTORY'</span><span class="token punctuation">,</span> value<span class="token punctuation">)</span>
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
</code></pre></div></li> <li><p>初始化的时候从本地存储获取数据</p> <div class="language-js extra-class"><pre class="language-js"><code><span class="token function">data</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">return</span> <span class="token punctuation">{</span>
    <span class="token operator">...</span><span class="token punctuation">.</span>
    searchHistories<span class="token operator">:</span> <span class="token function">getItem</span><span class="token punctuation">(</span><span class="token string">'TOUTIAO_SEARCH_HISTORY'</span><span class="token punctuation">)</span> <span class="token operator">||</span> <span class="token punctuation">[</span><span class="token punctuation">]</span> <span class="token comment">// 存储历史记录</span>
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
</code></pre></div></li> <li><p>测试本地存储功能是否实现</p></li></ol> <hr> <h2 id="_6-扩展-函数防抖和函数节流"><a href="#_6-扩展-函数防抖和函数节流" class="header-anchor">#</a> 6. 扩展：函数防抖和函数节流</h2> <p>干嘛的？限制函数调用的频率。</p> <p>为什么要限制？例如搜索的时候请求联想建议，没必要每次内容改变就发请求，当用户输入的很快的时候，中间的请求都是无意义的，浪费资源，没必要。</p> <h3 id="_6-1-函数防抖-debounce"><a href="#_6-1-函数防抖-debounce" class="header-anchor">#</a> 6.1 函数防抖（<code>Debounce</code>）</h3> <p><strong>概念：</strong> <code>在事件被触发n秒后再执行，如果在这n秒内又被触发，则重新计时。</code></p> <p><strong>生活中的实例：</strong> <code>如果有人进电梯（触发事件），那电梯将在10秒钟后出发（执行事件监听器），这时如果又有人进电梯了（在10秒内再次触发该事件），我们又得等10秒再出发（重新计时）。</code></p> <p>我们先使用第三方包 <a href="">lodash</a> 来体验什么是函数防抖：</p> <p>首先把 <code>lodash</code> 安装到项目中：</p> <div class="language-sh extra-class"><pre class="language-sh"><code><span class="token comment"># yarn add lodash</span>
<span class="token function">npm</span> i lodash
</code></pre></div><p>示例：</p> <div class="language-html extra-class"><pre class="language-html"><code><span class="token doctype"><span class="token punctuation">&lt;!</span><span class="token doctype-tag">DOCTYPE</span> <span class="token name">html</span><span class="token punctuation">&gt;</span></span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>html</span> <span class="token attr-name">lang</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>en<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>head</span><span class="token punctuation">&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>meta</span> <span class="token attr-name">charset</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>UTF-8<span class="token punctuation">&quot;</span></span> <span class="token punctuation">/&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>meta</span> <span class="token attr-name">name</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>viewport<span class="token punctuation">&quot;</span></span> <span class="token attr-name">content</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>width=device-width, initial-scale=1.0<span class="token punctuation">&quot;</span></span> <span class="token punctuation">/&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>meta</span> <span class="token attr-name">http-equiv</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>X-UA-Compatible<span class="token punctuation">&quot;</span></span> <span class="token attr-name">content</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>ie=edge<span class="token punctuation">&quot;</span></span> <span class="token punctuation">/&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>title</span><span class="token punctuation">&gt;</span></span>Document<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>title</span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>head</span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>body</span><span class="token punctuation">&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>script</span> <span class="token attr-name">src</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>./node_modules/lodash/lodash.js<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span><span class="token script"></span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>script</span><span class="token punctuation">&gt;</span></span>
    <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>script</span><span class="token punctuation">&gt;</span></span><span class="token script"><span class="token language-javascript">
      <span class="token comment">// lodash 会在全局提供一个成员：_</span>

      <span class="token comment">// _ 对象中有很多方法，其中有一个方法专门用于处理函数防抖</span>
      <span class="token comment">// 方法名：debounce</span>
      <span class="token comment">// 作用：函数防抖</span>
      <span class="token comment">// 使用方式：</span>

      <span class="token keyword">function</span> <span class="token function">fn</span><span class="token punctuation">(</span><span class="token parameter">foo</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
        console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">&quot;hello&quot;</span><span class="token punctuation">,</span> foo<span class="token punctuation">)</span><span class="token punctuation">;</span>
      <span class="token punctuation">}</span>

      <span class="token comment">// 正常的函数调用：立即调用，而且是一定会调用</span>
      <span class="token comment">// fn()</span>
      <span class="token comment">// fn()</span>
      <span class="token comment">// fn()</span>

      <span class="token comment">// 我们可以使用函数防抖把一个正常的函数变得不正常</span>
      <span class="token comment">// 两个参数：</span>
      <span class="token comment">//   参数1：函数</span>
      <span class="token comment">//   参数2：时间，单位是毫秒</span>
      <span class="token comment">// 返回值：函数</span>
      <span class="token comment">//   返回值函数的功能和 fn 和的功能是一样</span>
      <span class="token comment">//   唯一的区别就是经过了防抖处理</span>
      <span class="token keyword">const</span> newFn <span class="token operator">=</span> _<span class="token punctuation">.</span><span class="token function">debounce</span><span class="token punctuation">(</span>fn<span class="token punctuation">,</span> <span class="token number">1000</span><span class="token punctuation">)</span><span class="token punctuation">;</span>

      <span class="token comment">// 计时 1s</span>
      <span class="token function">newFn</span><span class="token punctuation">(</span><span class="token string">&quot;a&quot;</span><span class="token punctuation">)</span><span class="token punctuation">;</span>

      <span class="token comment">// 当你不到 1s 的时候，再次调用</span>
      <span class="token comment">// 先把之前的废掉，重新计时 1s</span>
      <span class="token function">newFn</span><span class="token punctuation">(</span><span class="token string">&quot;b&quot;</span><span class="token punctuation">)</span><span class="token punctuation">;</span>

      <span class="token function">newFn</span><span class="token punctuation">(</span><span class="token string">&quot;b&quot;</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
      <span class="token function">newFn</span><span class="token punctuation">(</span><span class="token string">&quot;b&quot;</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
      <span class="token comment">// newFn()</span>

      <span class="token comment">// he</span>
    </span></span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>script</span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>body</span><span class="token punctuation">&gt;</span></span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>html</span><span class="token punctuation">&gt;</span></span>
</code></pre></div><h3 id="_6-2-函数防抖实现原理"><a href="#_6-2-函数防抖实现原理" class="header-anchor">#</a> 6.2 函数防抖实现原理</h3> <p>函数防抖的实现原理：</p> <div class="language-js extra-class"><pre class="language-js"><code><span class="token keyword">function</span> <span class="token function">fn</span><span class="token punctuation">(</span><span class="token parameter">foo</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">&quot;hello&quot;</span><span class="token punctuation">,</span> foo<span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span>

<span class="token keyword">const</span> newFn <span class="token operator">=</span> <span class="token function">debounce</span><span class="token punctuation">(</span>fn<span class="token punctuation">,</span> <span class="token number">1000</span><span class="token punctuation">)</span><span class="token punctuation">;</span>

<span class="token comment">// 计时 1s</span>
<span class="token function">newFn</span><span class="token punctuation">(</span><span class="token number">123</span><span class="token punctuation">)</span><span class="token punctuation">;</span>

<span class="token comment">// 如果在 1s 之内重新调用</span>
<span class="token comment">//   先把之前的废除</span>
<span class="token comment">//   重新计时</span>
<span class="token function">newFn</span><span class="token punctuation">(</span><span class="token string">&quot;world&quot;</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token comment">// newFn()</span>

<span class="token keyword">function</span> <span class="token function">debounce</span><span class="token punctuation">(</span><span class="token parameter">callback<span class="token punctuation">,</span> time</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">let</span> timer <span class="token operator">=</span> <span class="token keyword">null</span><span class="token punctuation">;</span>
  <span class="token comment">// 函数参数中的 ... 表示接收剩余参数</span>
  <span class="token comment">// 它会把所有的参数收集到一个数组中</span>
  <span class="token keyword">return</span> <span class="token keyword">function</span><span class="token punctuation">(</span><span class="token parameter"><span class="token operator">...</span>args</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>args<span class="token punctuation">)</span><span class="token punctuation">;</span>
    window<span class="token punctuation">.</span><span class="token function">clearTimeout</span><span class="token punctuation">(</span>timer<span class="token punctuation">)</span><span class="token punctuation">;</span>
    timer <span class="token operator">=</span> <span class="token function">setTimeout</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">=&gt;</span> <span class="token punctuation">{</span>
      <span class="token comment">// 这里的 ... 表示数组展示操作符</span>
      <span class="token comment">// args[0], args[1], args[2] .........</span>
      <span class="token function">callback</span><span class="token punctuation">(</span><span class="token operator">...</span>args<span class="token punctuation">)</span><span class="token punctuation">;</span>
    <span class="token punctuation">}</span><span class="token punctuation">,</span> time<span class="token punctuation">)</span><span class="token punctuation">;</span>
  <span class="token punctuation">}</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span>
</code></pre></div><h3 id="_6-3-函数节流-throttle"><a href="#_6-3-函数节流-throttle" class="header-anchor">#</a> 6.3 函数节流（<code>Throttle</code>）</h3> <p><strong>概念：</strong> <code>规定一个单位时间，在这个单位时间内，只能有一次触发事件的回调函数执行，如果在同一个单位时间内某事件被触发多次，只有一次能生效。</code></p> <p>生活中的例子：<code>函数节流就是开枪游戏的射速，就算一直按着鼠标射击，也只会在规定射速内射出子弹。</code></p> <p>我们先用 <code>lodash</code> 来体验节流的使用方式：</p> <div class="language-js extra-class"><pre class="language-js"><code><span class="token keyword">function</span> <span class="token function">fn</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">&quot;------ fire ------&quot;</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span>

<span class="token comment">// 参数1：函数</span>
<span class="token comment">// 参数2：间隔时间</span>
<span class="token comment">// 返回值：函数（它的功能和保证的 fn 的功能是一样的，但是被进行了节流处理）</span>
<span class="token comment">// 第1次直接调用，之后的按照一定频率进行调用</span>
<span class="token keyword">const</span> newFn <span class="token operator">=</span> _<span class="token punctuation">.</span><span class="token function">throttle</span><span class="token punctuation">(</span>fn<span class="token punctuation">,</span> <span class="token number">2000</span><span class="token punctuation">)</span><span class="token punctuation">;</span>

<span class="token comment">// newFn()</span>
<span class="token comment">// newFn()</span>

<span class="token function">setInterval</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">=&gt;</span> <span class="token punctuation">{</span>
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">&quot;鼠标点击&quot;</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
  <span class="token function">newFn</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span><span class="token punctuation">,</span> <span class="token number">200</span><span class="token punctuation">)</span><span class="token punctuation">;</span>

<span class="token comment">// 一上来就调用一次</span>
<span class="token comment">// newFn()</span>

<span class="token comment">// // 之后的调用，开始计时 1s</span>
<span class="token comment">// newFn()</span>

<span class="token comment">// // 1s 之内所有的调用只有1次</span>
<span class="token comment">// newFn()</span>
<span class="token comment">// newFn()</span>
<span class="token comment">// newFn()</span>
<span class="token comment">// newFn()</span>
<span class="token comment">// newFn()</span>
</code></pre></div><h3 id="_6-4-函数节流实现原理"><a href="#_6-4-函数节流实现原理" class="header-anchor">#</a> 6.4 函数节流实现原理</h3> <div class="language-js extra-class"><pre class="language-js"><code><span class="token keyword">function</span> <span class="token function">throttle</span><span class="token punctuation">(</span><span class="token parameter">callback<span class="token punctuation">,</span> interval</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token comment">// 最后一次的调用时间</span>
  <span class="token keyword">let</span> lastTime <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span>

  <span class="token comment">// 定时器</span>
  <span class="token keyword">let</span> timer <span class="token operator">=</span> <span class="token keyword">null</span><span class="token punctuation">;</span>

  <span class="token comment">// 返回一个函数</span>
  <span class="token keyword">return</span> <span class="token keyword">function</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    <span class="token comment">// 清除定时器</span>
    <span class="token function">clearTimeout</span><span class="token punctuation">(</span>timer<span class="token punctuation">)</span><span class="token punctuation">;</span>

    <span class="token comment">// 当前最新时间</span>
    <span class="token keyword">let</span> nowTime <span class="token operator">=</span> Date<span class="token punctuation">.</span><span class="token function">now</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span>

    <span class="token comment">// 如果当前最新时间 - 上一次时间 &gt;= 时间间隔</span>
    <span class="token comment">// 或者没有上一次时间，那就立即调用</span>
    <span class="token keyword">if</span> <span class="token punctuation">(</span>nowTime <span class="token operator">-</span> lastTime <span class="token operator">&gt;=</span> interval<span class="token punctuation">)</span> <span class="token punctuation">{</span>
      <span class="token function">callback</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span>

      <span class="token comment">// 记录最后一次的调用时间</span>
      <span class="token comment">// 1</span>
      lastTime <span class="token operator">=</span> nowTime<span class="token punctuation">;</span>
    <span class="token punctuation">}</span> <span class="token keyword">else</span> <span class="token punctuation">{</span>
      timer <span class="token operator">=</span> <span class="token function">setTimeout</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">=&gt;</span> <span class="token punctuation">{</span>
        <span class="token function">callback</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
      <span class="token punctuation">}</span><span class="token punctuation">,</span> interval<span class="token punctuation">)</span><span class="token punctuation">;</span>
    <span class="token punctuation">}</span>
  <span class="token punctuation">}</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span>

<span class="token keyword">const</span> fn <span class="token operator">=</span> <span class="token function">throttle</span><span class="token punctuation">(</span>函数<span class="token punctuation">,</span> <span class="token number">1000</span><span class="token punctuation">)</span><span class="token punctuation">;</span>

<span class="token comment">//</span>
<span class="token function">fn</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span>

<span class="token function">fn</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span>

<span class="token function">fn</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
</code></pre></div><h3 id="_6-5-函数节流或者防抖的相关场景"><a href="#_6-5-函数节流或者防抖的相关场景" class="header-anchor">#</a> 6.5 函数节流或者防抖的相关场景</h3> <ul><li>建议</li> <li><code>window.resize</code> 事件处理</li> <li>页面的滚动事件</li></ul> <h3 id="_6-6-总结"><a href="#_6-6-总结" class="header-anchor">#</a> 6.6 总结</h3> <ul><li>函数防抖和函数节流都是防止某一时间频繁触发，但是这两兄弟之间的特性却不一样。
<ul><li><code>search</code> 搜索联想，用户在不断输入值时，用防抖来节约请求资源。</li> <li><code>window</code> 触发 <code>resize</code> 的时候，不断的调整浏览器窗口大小会不断的触发这个事件，用防抖来让其只触发一次</li></ul></li> <li>函数防抖是某一段时间内只执行一次，而函数节流是间隔时间执行。
<ul><li>鼠标不断点击触发，<code>mousedown</code> (单位时间内只触发一次)</li> <li>监听滚动事件，比如是否滑到底部自动加载更多，用 <code>throttle</code> 来判断</li></ul></li></ul> <h2 id="_7-扩展-lodash-函数库"><a href="#_7-扩展-lodash-函数库" class="header-anchor">#</a> 7. 扩展：<code>lodash</code> 函数库</h2> <p><code>lodash</code> 是一个常用工具函数库，它里面封装了好多常用的工具函数：</p> <ul><li>官方文档： https://lodash.com/</li> <li>翻译的中文文档：https://www.lodashjs.com/</li></ul> <blockquote><p>在 <code>lodas</code>h 之前还有一个 JavaScript 工具函数库：<a href="https://underscorejs.org/" target="_blank" rel="noopener noreferrer">underscore<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a>，<code>lodash</code> 模仿 <code>underscop</code>e 自己重新实现了一遍，它相比 underscore 最大的好处是它支持按需加载。<code>underscope</code> 不支持按需加载。</p></blockquote></div> <footer class="page-edit"><!----> <!----></footer> <!----> </main></div><div class="global-ui"><!----></div></div>
    <script src="/heima2020/assets/js/app.e2adc9d2.js" defer></script><script src="/heima2020/assets/js/2.7389c9d3.js" defer></script><script src="/heima2020/assets/js/21.85e67b4a.js" defer></script>
  </body>
</html>
